package com.heima.article.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.heima.article.entity.ApArticle;
import com.heima.article.entity.ApArticleContent;
import com.heima.article.entity.ApAuthor;
import com.heima.article.mapper.ApArticleMapper;
import com.heima.article.service.ApArticleContentService;
import com.heima.article.service.ApArticleService;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.heima.article.service.ApAuthorService;
import com.heima.article.service.ArticleFreemarkerService;
import com.heima.common.constants.message.Article2EsConstants;
import com.heima.common.enums.AppHttpCodeEnum;
import com.heima.common.exception.LeadException;
import com.heima.common.util.BeanHelper;
import com.heima.common.util.JsonUtils;
import com.heima.model.article.dtos.ArticleDto;
import com.heima.model.article.dtos.ArticleHomeDto;
import com.heima.model.article.dtos.AuthorDto;
import com.heima.model.media.dtos.WmNewsResultDTO;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.kafka.core.KafkaTemplate;
import org.springframework.scheduling.annotation.Async;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.CollectionUtils;

import java.util.Collections;
import java.util.Date;
import java.util.List;
import java.util.Map;

import static com.heima.common.constants.message.Article2EsConstants.ARTICLE_2_ES_TOPIC;
import static com.heima.common.constants.message.Article2EsConstants.ES_DELETE_ARTICLE_TOPIC;

/**
 * <p>
 * 文章信息表，存储已发布的文章 服务实现类
 * </p>
 *
 * @author RMY
 * @since 2021-11-24
 */
@Slf4j
@Service
public class ApArticleServiceImpl extends ServiceImpl<ApArticleMapper, ApArticle> implements ApArticleService {
    @Autowired
    private ApAuthorService apAuthorService;
    @Autowired
    private ApArticleContentService apArticleContentService;
    @Autowired
    private ArticleFreemarkerService articleFreemarkerService;
    @Autowired
    private KafkaTemplate kafkaTemplate;
    /**
     * 保存article
     * @param dto
     * @return
     */
    @Override
    @Transactional
    public Long saveArticle(WmNewsResultDTO dto) {
        //1.保存apArticle
        //1.1封装apArticle
        //1.2查询是否有改文章，没有就新增，有就修改
        QueryWrapper<ApArticle> qw = new QueryWrapper<>();
        qw.lambda().eq(ApArticle::getWmNewsId,dto.getId());
        ApArticle apArticle = getOne(qw);
        if (apArticle == null){
            apArticle = new ApArticle();
            apArticle.setWmNewsId(dto.getWmUserId());
            //1.2.1查询作者的id，封装apArticle
            ApAuthor apAuthor = apAuthorService.findByWmUserId(dto.getWmUserId());
            if (apAuthor != null){
                apArticle.setAuthorId(apAuthor.getId());
                apArticle.setAuthorName(apAuthor.getName());
            }
            apArticle.setLikes(0L);
            apArticle.setCollection(0L);
            apArticle.setComments(0L);
            apArticle.setViews(0L);
            apArticle.setIsComment(true);
            apArticle.setIsForward(true);
            apArticle.setIsDown(false);
            apArticle.setIsDelete(false);
            apArticle.setCreatedTime(new Date());
        }
        //1.3修改
        apArticle.setTitle(dto.getTitle());
        apArticle.setChannelId(dto.getChannelId());
        apArticle.setLayout(dto.getType());
        apArticle.setImages(dto.getImages());
        apArticle.setLabels(dto.getLabels());
        apArticle.setPublishTime(dto.getPublishTime()==null?new Date():dto.getPublishTime());
        boolean b = saveOrUpdate(apArticle);
        if (!b){
            throw new LeadException(AppHttpCodeEnum.SERVER_ERROR);
        }
        //2.保存content
        ApArticleContent apArticleContent = new ApArticleContent();
        apArticleContent.setArticleId(apArticle.getId());
        apArticleContent.setContent(dto.getContent());
        boolean b1 = apArticleContentService.saveOrUpdate(apArticleContent);
        if (!b1){
            throw new LeadException(AppHttpCodeEnum.SERVER_ERROR);
        }
        //上传静态文件
        articleFreemarkerService.buildArticleToMinIO(apArticle,dto.getContent());
        //        创建Es的索引库,msg可以传文章id，也可以传文章内容
        ArticleDto articleDto = BeanHelper.copyProperties(apArticle, ArticleDto.class);
        articleDto.setContent(dto.getContent());
        kafkaTemplate.send(ARTICLE_2_ES_TOPIC, JsonUtils.toString(articleDto));
        return apArticle.getId();
    }
    /**
     * 加载首页文章
     * @return
     */
    @Override
    public List<ArticleDto> load(ArticleHomeDto dto, int i) {
        //初始化每页个数
        Integer size = dto.getSize();
        //1.判断参数 i-1 加载所有 i-2 加载最新
        QueryWrapper<ApArticle> qw = new QueryWrapper<>();
        if (dto.getChannelId()!=null && dto.getChannelId()!=0){
            qw.lambda().eq(ApArticle::getChannelId,dto.getChannelId());
        }
        if (i == 1){
            qw.lambda().le(ApArticle::getCreatedTime,dto.getMinTime());
        }else {
            qw.lambda().ge(ApArticle::getCreatedTime,dto.getMaxTime());
        }
        //2.每页大小
        if (size!=null && size>0){
            size = 10;//默认
        }
        qw.lambda().eq(ApArticle::getIsDown,false).eq(ApArticle::getIsDelete,false).orderByDesc(ApArticle::getPublishTime);
        //分页查询
        IPage<ApArticle> iPage = new Page<>(1, size);
        IPage<ApArticle> page = this.page(iPage,qw);
        //判断结果是否为空
        if (page!=null && !CollectionUtils.isEmpty(page.getRecords())){
            //返回最终结果
            List<ArticleDto> articleDtoList = BeanHelper.copyWithCollection(page.getRecords(), ArticleDto.class);
            return articleDtoList;

        }
        return Collections.emptyList();
    }

    /**
     *上架或下架
     * @param map
     */

    @Override
    public void upOrDown(Map<String, Long> map) {
        ApArticle apArticle = new ApArticle();
        Long articleId = map.get("articleId");
        apArticle.setId(articleId);
        apArticle.setIsDown(map.get("enable")==0);
        updateById(apArticle);
        // 判断是上架还是下架
        if (map.get("enable") == 0) { // 下架
            // 删除索引库的该数据
            kafkaTemplate.send(ES_DELETE_ARTICLE_TOPIC, articleId.toString());
        }else { // 上架
            // 查询该文章的数据和内容
            apArticle = getById(articleId);
            ApArticleContent articleContent = apArticleContentService.getById(articleId);
            ArticleDto articleDto = BeanHelper.copyProperties(apArticle, ArticleDto.class);
            articleDto.setContent(articleContent.getContent());
            // 在索引库添加该条数据
            kafkaTemplate.send(ARTICLE_2_ES_TOPIC, JsonUtils.toString(articleDto));
            log.info("上架创建索引库{}", articleDto);
        }
    }

    /**
     * 分页查询文章信息
     * @param page
     * @param size
     * @return
     */
    @Override
    public List<ArticleDto> findArticleByPage(int page, int size) {
//        设置分页
        IPage<ApArticle> iPage = new Page<>(page,size);

        List<ArticleDto> list = getBaseMapper().selectArticleAndContent(iPage);

        return list;
    }
}
